import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:get/get.dart';
import 'package:ichinesereader/constants.dart';
import 'package:ichinesereader/controller/authentication.dart';
import 'package:ichinesereader/controller/cache.dart';
import 'package:ichinesereader/models/assessment/assessmentCountResult.dart';
import 'package:ichinesereader/models/class/ClassResp.dart';
import 'package:ichinesereader/models/class/classSettingsResult.dart';
import 'package:ichinesereader/models/common/LeaderBoard.dart';
import 'package:ichinesereader/models/common/LevelPercentage.dart';
import 'package:ichinesereader/models/common/MessageProperty.dart';
import 'package:ichinesereader/models/common/MyAchievement.dart';
import 'package:ichinesereader/models/common/Passwords.dart';
import 'package:ichinesereader/models/common/ProfileDTO.dart';
import 'package:ichinesereader/models/common/ProfileResult.dart';
import 'package:ichinesereader/models/common/ReadRanking.dart';
import 'package:ichinesereader/models/individual/profileIndividual.dart';
import 'package:ichinesereader/models/parent/linkChildDto.dart';
import 'package:ichinesereader/models/parent/miniProfile.dart';
import 'package:ichinesereader/models/parent/profileParent.dart';
import 'package:ichinesereader/models/student/ProfileStudent.dart';
import 'package:ichinesereader/models/teacher/TeacherClass.dart';
import 'package:ichinesereader/service/user.dart';
import 'package:ichinesereader/models/common/StatusMessageResult.dart';
import 'package:hive_flutter/hive_flutter.dart';
import 'package:universal_html/html.dart';
import '../models/common/Settings.dart';
import 'package:ichinesereader/utils/log.dart';

class UserController extends GetxController with StateMixin<dynamic> {
  var box = Hive.box('appconfig');

  Rx<StatusMessageResult> _statusMessageResult =
      Rx<StatusMessageResult>(StatusMessageResult());

  var _currentProfileSettings;
  Rx<StatusMessageResult> get statusMessageResult => this._statusMessageResult;

  LoginController _loginController = Get.find();

  List<TeacherClass> _myClasses = <TeacherClass>[].obs;
  List<TeacherClass> _myClassesForStudent = <TeacherClass>[].obs;
  List<TeacherClass> _myClassesForSchoolAdmin = <TeacherClass>[].obs;
  bool running = false;
  Rx<TeacherClass> _currentClass = Rx<TeacherClass>(TeacherClass());
  Rx<TeacherClass> _currentStudentClass = Rx<TeacherClass>(TeacherClass());
  Rx<TeacherClass> _currentSchoolAdminClass = Rx<TeacherClass>(TeacherClass());
  Rx<ProfileStudent> _currentChild = Rx<ProfileStudent>(ProfileStudent());

  Rx<ProfileResult> _profileResult = Rx<ProfileResult>(ProfileResult());
  List<ReadRanking> _rankingsWord = <ReadRanking>[].obs;
  List<ReadRanking> _rankingsClass = <ReadRanking>[].obs;
  List<MyAchievement> _achievements = <MyAchievement>[].obs;
  List<ProfileStudent> _parentChildren = <ProfileStudent>[].obs;
  Rx<ClassResp> _parentSelctedClass = Rx<ClassResp>(ClassResp());
  List<ClassResp> _parentClassOptions = <ClassResp>[].obs;

  RxInt _newAssessmentCount = 0.obs;
  RxInt get newAssessmentCount => this._newAssessmentCount;

  RxString _selectedLang = 'ENG'.obs;
  RxInt _selectedTheme = 0.obs;
  RxString get selectedLang => this._selectedLang;
  RxInt get selectedTheme => this._selectedTheme;

  Rx<Locale> _userLocale = Rx<Locale>(Locale('en', 'US'));

  late bool isDarkTheme;
  late bool isUsernameAvailable;

  Rx<ProfileResult> get profile => this._profileResult;
  List<ReadRanking> get rankingsWord => this._rankingsWord;
  List<ReadRanking> get rankingsClass => this._rankingsClass;

  Locale get userLocale => this._userLocale.value;
  List<TeacherClass> get myClasses => this._myClasses;
  List<TeacherClass> get myClassesForStudent => this._myClassesForStudent;
  List<TeacherClass> get myClassesForSchoolAdmin =>
      this._myClassesForSchoolAdmin;
  List<ProfileStudent> get parentChildren => this._parentChildren;

  Rx<ProfileStudent> get currentChild => this._currentChild;
  Rx<TeacherClass> get currentClass => this._currentClass;
  TeacherClass get currentStudentClass => this._currentStudentClass.value;
  TeacherClass get currentSchoolAdminClass =>
      this._currentSchoolAdminClass.value;
  List<MyAchievement> get achievements => this._achievements;

  UserServiceProvider userServiceProvider = new UserServiceProvider();
  StatusMessageResult _statusResult = new StatusMessageResult();
  final hasPlacement = false.obs;

  RxBool _hasAssignment = false.obs;
  RxBool get hasAssignment => this._hasAssignment;
  Rx<ClassResp> get parentSelctedClass => this._parentSelctedClass;
  List<ClassResp> get parentClassOptions => this._parentClassOptions;

  @override
  void onInit() {
    isDarkTheme = false;
    int locale = box.get('locale', defaultValue: 0);
    if (locale == 0) this._selectedLang.value = 'ENG';
    if (locale == 1) this._selectedLang.value = '简体';
    if (locale == 2) this._selectedLang.value = '繁体';
    super.onInit();
  }

  @override
  dispose() {
    super.dispose();
  }

  void setMyLang(String? lang) async {
    this._selectedLang.value = lang ?? 'ENG';
    int langNum = 0;
    switch (lang) {
      case 'ENG':
        langNum = 0;
        break;
      case '简体':
        langNum = 1;
        break;
      case '繁体':
        langNum = 2;
        break;
      default:
        langNum = 0;
    }

    this._profileResult.value.lang = langNum;
    box.put('locale', langNum);

    bool isSchoolAdmin = box.get(CacheManagerKey['nanhairole'].toString()) ==
        Constants.NanhaiRole_SchoolAdmin;
    if (!isSchoolAdmin) {
      _updateProfileLanguageSetting(langNum);
    }

    if (GetPlatform.isWeb) {
      window.localStorage['locale'] = langNum.toString();
      //需要兼容老版本的网页页面
      switch (langNum) {
        case 0:
          window.localStorage['them_language'] = 'ENGLISH';
          break;
        case 1:
          window.localStorage['them_language'] = 'SIMPLIFIED';
          break;
        case 2:
          window.localStorage['them_language'] = 'TRADITIONAL';
          break;
        default:
          window.localStorage['them_language'] = 'ENGLISH';
      }
    }
  }

  void setMyTheme(int? theme) async {
    this._selectedTheme.value = theme ?? 0;
    box.put('theme', this._selectedTheme.value);
    if (GetPlatform.isWeb) {
      window.localStorage['theme'] = this._selectedTheme.value.toString();
    }
  }

  Future<void> setCurrentProfileSettings(Settings? settings) async {
    try {
      this._currentProfileSettings = settings;
    } catch (error) {
      Log.debug(error);
    }
  }

  Settings? getCurrentProfileSettings() {
    try {
      return this._currentProfileSettings;
    } catch (error) {
      Log.debug(error);
      return null;
    }
  }

  // simple or traditional
  void setLanguage(String? language) async {
    box.put('UserLanguage', language!);
    if (GetPlatform.isWeb) {
      window.localStorage['language'] = language;
    }
  }

  // pinyin or no pinyin
  void setPinyin(bool? pinyin) async {
    box.put('UserPinyin', pinyin);
  }

  // mandarin or contonese
  void setLang(String? lang) async {
    box.put('UserLang', lang ?? 'Simplified');
    if (GetPlatform.isWeb) {
      window.localStorage['lang'] = lang ?? 'Mandarin';
    }
  }

  void setMyProfile(ProfileResult profile) async {
    this._profileResult.value = profile;
  }

// for teacher class only
  void setCurrentClass(TeacherClass tc) async {
    if (tc.classId != this._currentClass.value.classId) {
      this._currentClass.value = tc;
      await box.put(CacheManagerKey['currentclass'].toString(), tc.classId);
      change(this._currentClass, status: RxStatus.success());
    }
  }

//for student class only
  void setCurrentStudentClass(TeacherClass tc) async {
    if (tc.classId != this.currentStudentClass.classId)
      this._currentStudentClass.value = tc;
    await box.put(CacheManagerKey['currentclass'].toString(),
        _currentStudentClass.value.classId.toString());
    change(this._currentStudentClass, status: RxStatus.success());
  }

//for school admin only
  void setCurrentSchoolAdminClass(TeacherClass tc) async {
    if (tc.classId != this.currentSchoolAdminClass.classId)
      this._currentSchoolAdminClass.value = tc;
    await box.put(CacheManagerKey['currentclass'].toString(),
        _currentSchoolAdminClass.value.classId.toString());
    change(this._currentSchoolAdminClass, status: RxStatus.success());
  }

  // for parent child only
  Future<void> setCurrentChild(ProfileStudent ch) async {
    this._currentChild.value = ch;
    await box.put(CacheManagerKey['currentchild'].toString(), ch.userName);
    change(this._currentChild, status: RxStatus.success());
  }

  TeacherClass getCurrentClass() {
    return this._currentClass.value;
  }

  TeacherClass getCurrentStudentClass() {
    return this._currentStudentClass.value;
  }

  TeacherClass getCurrentSchoolAdminClass() {
    return this._currentSchoolAdminClass.value;
  }

  ProfileStudent getCurrentChild() {
    return this._currentChild.value;
  }

  void checkUsernameAvailable(String userName) async {
    isUsernameAvailable = await userServiceProvider.usernameAvailable(userName);
  }

  Future<List<TeacherClass>> fetchMyClasses() async {
    try {
      _myClasses.clear();
      var response = await userServiceProvider.getClasses();
      if (response.statusCode == 200) {
        var data = teacherClassFromJson(response.bodyString);
        _myClasses.assignAll(data);
        change(_myClasses, status: RxStatus.success());
        if (data.length > 0) {
          if (this._currentClass.value.classId == null ||
              this._currentClass.value.classId == '') {
            this._currentClass.value = data[0];
          } else {
            bool isInClasses = false;
            data.forEach((element) {
              if (element.classId == this._currentClass.value.classId)
                isInClasses = true;
            });
            if (!isInClasses) this._currentClass.value = data[0];
          }
          Log.debug(this._currentClass.value.classId.toString());
          box.put(CacheManagerKey['currentclass'].toString(),
              this._currentClass.value.classId.toString());

          change(this._currentClass, status: RxStatus.success());

          if (GetPlatform.isWeb) {
            document.cookie =
                "nanhaiV4.8TeacherClassSelected=${this._currentClass.value.classId.toString()};path=/";
          }
        }
      }
    } catch (error) {
      Log.debug(error);
    }
    return _myClasses;
  }

  void fetchMyClassesForSchoolAdmin() async {
    try {
      var response = await userServiceProvider.getClasses();
      if (response.statusCode == 200) {
        var data = teacherClassFromJson(response.bodyString);
        _myClassesForSchoolAdmin.assignAll(data);
        change(_myClassesForSchoolAdmin, status: RxStatus.success());
        if (data.length > 0) {
          _currentSchoolAdminClass.value = data[0];
          await box.put(CacheManagerKey['currentclass'].toString(),
              _currentSchoolAdminClass.value.classId.toString());
        }
      }
    } catch (error) {
      Log.debug(error);
    }
  }

  void fetchMyClassesForStuent() async {
    try {
      var response = await userServiceProvider.getClasses();
      if (response.statusCode == 200) {
        var data = teacherClassFromJson(response.bodyString);
        _myClassesForStudent.assignAll(data);
        change(_myClassesForStudent, status: RxStatus.success());
        if (data.length > 0) {
          _currentStudentClass.value = data[0];
          await box.put(CacheManagerKey['currentclass'].toString(),
              _currentStudentClass.value.classId.toString());
        }
      }
    } catch (error) {
      Log.debug(error);
    }
  }

  Future<void> getProfile() async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response = await userServiceProvider.getProfileService();
      if (response.statusCode == 200) {
        _profileResult.value =
            ProfileResult.fromJson(json.decode(response.bodyString));

        if (_loginController.userRole.value == Constants.NanhaiRole_Student) {
          var tprofile = profileStudentFromJson(response.bodyString);
          var classId = box.get(CacheManagerKey['currentclass'].toString());

          if (classId != null && classId != '') {
            userServiceProvider
                .getClassSettingsByClassId(classId)
                .then((sresponse) {
              if (sresponse.statusCode == 200) {
                var _settings =
                    classSettingsResultFromJson(sresponse.bodyString);
                box.put('interfaceChinese', _settings.result?.interfaceChinese);
                box.put('evaluation', _settings.result?.evaluation);
                if (_settings.result != null) {
                  _profileResult.value.settings?.evaluation =
                      _settings.result?.evaluation ?? true;
                  _profileResult.value.settings?.vocabulary =
                      _settings.result?.vocabulary ?? true;
                  _profileResult.value.settings?.placementTest =
                      _settings.result?.placementTest ?? true;
                  _profileResult.value.settings?.quizThreshold =
                      _settings.result?.quizThreshold ?? 75;
                  _profileResult.value.settings?.interfaceChinese =
                      _settings.result?.interfaceChinese ?? true;
                }
              }
            });
          }

          if (tprofile.myAchievements != null) {
            _loginController.userName.value = tprofile.userName ?? '';
            this
                ._achievements
                .assignAll(tprofile.myAchievements as List<MyAchievement>);
          }
        }

        if (_loginController.userRole.value ==
            Constants.NanhaiRole_Individual) {
          var tprofile = profileIndividualFromJson(response.bodyString);
          if (tprofile.myAchievements != null) {
            _loginController.userName.value = tprofile.userName ?? '';
            this
                ._achievements
                .assignAll(tprofile.myAchievements as List<MyAchievement>);
          }
        }
        if (_loginController.userRole.value == Constants.NanhaiRole_Parent) {
          var pprofile = profileParentFromJson(response.bodyString);
          if (pprofile.userName != null) {
            _loginController.userName.value = pprofile.userName ?? '';

            this
                ._parentChildren
                .assignAll(pprofile.children as List<ProfileStudent>);

            if (this._parentChildren.length > 0) {
              this._parentChildren.sort((a, b) => a.firstName!
                  .toLowerCase()
                  .compareTo(b.firstName!.toLowerCase()));
              this._currentChild.value = this._parentChildren[0];
              change(_parentChildren, status: RxStatus.success());
            }
            this.getParentClassOptions(null);
          }
        }
        change(_profileResult, status: RxStatus.success());

        if (this._achievements.isNotEmpty) {
          change(_achievements, status: RxStatus.success());
        }
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    _statusMessageResult.value = _statusResult;
  }

  Future<StatusMessageResult> updateProfile(ProfileDTO profile) async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response = await userServiceProvider.updateProfileService(profile);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';

        bool isParent = box.get(CacheManagerKey['nanhairole'].toString()) ==
            Constants.NanhaiRole_Parent;
        if (!isParent) {
          this._profileResult.value.settings?.lang = profile.settings?.lang;
          this._profileResult.value.settings?.language =
              profile.settings?.language;
          this._profileResult.value.settings?.pinyin = profile.settings?.pinyin;

          box.put(CacheManagerKey['profilesettings'].toString(),
              json.encode(this._profileResult.value.settings));
        }
      } else {
        _statusResult.status = 0;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  void checkPlacementTest() async {
    try {
      _statusResult = new StatusMessageResult();
      var response = await userServiceProvider.hasPlacementTest();
      if (response.statusCode == 200) {
        var data = assessmentCountResultFromJson(response.body);
        if (data.result != null) {
          if (data.result!.count!.toInt() > 0) hasPlacement.value = true;
        }
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        Log.debug(response.body);
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    }
    _statusMessageResult.value = _statusResult;
  }

  Future<bool> checkNewAssignment() async {
    try {
      var response = await userServiceProvider.hasNewAssignments();
      if (response.statusCode == 200) {
        if (response.bodyString != null && response.bodyString == 'true') {
          _hasAssignment.value = true;
        } else {
          _hasAssignment.value = false;
        }
      } else {
        _hasAssignment.value = false;
      }
      change(_hasAssignment, status: RxStatus.success());
    } catch (error) {
      Log.debug(error);
    }
    return _hasAssignment.value;
  }

  Future<int> getNewAssessmentAccount() async {
    int _assessmentNum = 0;
    try {
      var response = await userServiceProvider.hasNewAssessments();
      if (response.statusCode == 200) {
        var data = assessmentCountResultFromJson(response.bodyString);
        if (data.result != null) {
          if (data.result!.count!.toInt() > 0)
            this._newAssessmentCount.value = data.result!.count!.toInt();
          _assessmentNum = data.result!.count!.toInt();
        }
        change(this._newAssessmentCount.value, status: RxStatus.success());
      } else {
        _assessmentNum = 0;
        Log.debug(response.bodyString);
      }
    } catch (error) {
      _assessmentNum = 0;
      Log.debug(error);
    }
    return _assessmentNum;
  }

  Future<StatusMessageResult> changeUserPassword(Passwords passwords) async {
    try {
      _statusResult = new StatusMessageResult();
      EasyLoading.show();
      var response = await userServiceProvider.changeUserPassword(passwords);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  Future<StatusMessageResult> resetStrongUserPassword(
      Passwords passwords) async {
    try {
      _statusResult = new StatusMessageResult();
      EasyLoading.show();
      var response = await userServiceProvider.changeUserPassword(passwords);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        MessagePropertyResult _mpr =
            messagePropertyResultFromJson(response.bodyString);
        _statusResult.status = response.statusCode;
        _statusResult.message = _mpr.message?.message ??
            'Password reset failed, please try again later!'.tr;
      }
    } catch (error) {
      Log.debug(error);
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  //resetStudentPassword
  Future<StatusMessageResult> resetStudentPassword(
      String userName, String password) async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response =
          await userServiceProvider.resetStudentPassword(userName, password);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  //resetTeacherPassword
  Future<StatusMessageResult> resetTeacherPassword(
      String userName, String password) async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response =
          await userServiceProvider.resetTeacherPassword(userName, password);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  Future<StatusMessageResult> resetTeacherEmail(
      String userName, String email) async {
    try {
      _statusResult = new StatusMessageResult();
      EasyLoading.show();
      var response =
          await userServiceProvider.resetTeacherEmail(userName, email);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  void getLeaderBoardWord() async {
    try {
      EasyLoading.show();
      var response = await userServiceProvider.getLeaderBoardAll();
      if (response.statusCode == 200) {
        var data = leaderBoardFromJson(response.bodyString);
        if (data.result != null) {
          this._rankingsWord.assignAll(data.result?.data as List<ReadRanking>);
          change(this._rankingsWord, status: RxStatus.success());
        } else {
          change(this._rankingsWord, status: RxStatus.empty());
        }
      } else {
        change(this._rankingsWord, status: RxStatus.empty());
      }
    } catch (error) {
      //change(null, status: RxStatus.empty());
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
  }

  void getLeaderBoardClass(String classId) async {
    try {
      EasyLoading.show();
      var response = await userServiceProvider.getLeaderBoardByClass(classId);
      if (response.statusCode == 200) {
        var data = readRankingFromJson(response.bodyString);
        if (data.length > 0) {
          this._rankingsClass.assignAll(data);
          change(this._rankingsClass, status: RxStatus.success());
        } else {
          change(this._rankingsClass, status: RxStatus.empty());
        }
      } else {
        change(this._rankingsClass, status: RxStatus.empty());
      }
    } catch (error) {
      //change(this._rankingsClass, status: RxStatus.empty());
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
  }

  void refreshLevelPercentage() async {
    try {
      var response = await userServiceProvider.refreshLevelPercentage();
      if (response.statusCode == 200) {
        var data = levelPercentageFromJson(response.bodyString);
        this._profileResult.value.levelPercentage = data.levelPercentage;
        this._profileResult.value.level =
            data.levelDisplayName?.replaceAll('Level ', '') ?? '1';
        //Log.debug('${data.levelDisplayName} -  ${data.levelPercentage.toString()}');
        box.put("UserLevel",
            data.levelDisplayName?.replaceAll('Level ', '') ?? '1');
        box.put("UserLevelPercentage", data.levelPercentage ?? 0);
        change(this._profileResult, status: RxStatus.success());
      }
    } catch (error) {
      Log.debug(error);
    }
  }

  Future<StatusMessageResult> unlinkChild(String userName) async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response = await userServiceProvider.unlinkChild(userName);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  Future<StatusMessageResult> updateChild(
      String userName, MiniProfile profile) async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response = await userServiceProvider.updateChild(userName, profile);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  Future<StatusMessageResult> linkChild(LinkChildDto dto) async {
    try {
      EasyLoading.show();
      _statusResult = new StatusMessageResult();
      var response = await userServiceProvider.linkChild(dto);
      if (response.statusCode == 200) {
        _statusResult.status = 1000;
        _statusResult.message = 'Success';
      } else {
        _statusResult.status = response.statusCode;
        _statusResult.message = 'Failed';
      }
    } catch (error) {
      _statusResult.status = 0;
      _statusResult.message = 'Oops, something wrong ...'.tr;
      Log.debug(error);
    } finally {
      EasyLoading.dismiss();
    }
    return _statusResult;
  }

  void getParentClassOptions(String? userName) {
    var childUserName = this._parentChildren.first.userName;
    if (userName == null) {
      childUserName = box.get(CacheManagerKey['currentchild'].toString());
    } else {
      childUserName = userName;
    }
    if (childUserName!.isEmpty) {
      childUserName = this._parentChildren.first.userName;
    }
    var child = this
        ._parentChildren
        .firstWhereOrNull((element) => element.userName == childUserName);
    if (child != null) {
      this.setCurrentChild(child);

      var classes = child.classResps;
      this._parentClassOptions.clear();
      if (classes != null && classes.isNotEmpty) {
        this._parentClassOptions.addAll(classes);
        this._parentSelctedClass.value = classes[0];
      }
    }

    // change(_parentClassOptions, status: RxStatus.success());
  }

  void updateParentSelectedClass(ClassResp classInfo) {
    change(null, status: RxStatus.loading());
    this._parentSelctedClass.value = classInfo;
    change(_parentSelctedClass, status: RxStatus.success());
  }

//////////////////////theme ///////////////////////////////////////
  ThemeMode get themeStateFromProfileSettings =>
      _getThemeFromProfile() ? ThemeMode.dark : ThemeMode.light;

  bool _getThemeFromProfile() {
    // to get thememode in profile, default is light and eye protection mode
    return Get.isDarkMode;
  }

  _updateProfileThemeSetting(bool isDarkTheme) {
    try {
      if (isDarkTheme) {
        box.put('theme', 1);
      } else {
        box.put('theme', 0);
      }
      bool isSchoolAdmin = box.get(CacheManagerKey['nanhairole'].toString()) ==
          Constants.NanhaiRole_SchoolAdmin;
      if (!isSchoolAdmin) {
        ProfileDTO newProfile = new ProfileDTO(
            firstName: this.profile.value.firstName,
            lastName: this.profile.value.lastName,
            email: this.profile.value.email,
            settings: this.profile.value.settings);
        updateProfile(newProfile);
      }
    } catch (e) {
      Log.debug(e);
    }
  }

// 使用系统dart模式来当作护眼模式；ligth模式为正常阅读模式
  void changeTheme({required bool isDarkMode}) {
    if (isDarkMode) {
      isDarkTheme = true;
      _updateProfileThemeSetting(true);
      _changeThemeMode(ThemeMode.dark);
    } else {
      isDarkTheme = false;
      _updateProfileThemeSetting(false);
      _changeThemeMode(ThemeMode.light);
    }
  }

  void _changeThemeMode(ThemeMode themeMode) => Get.changeThemeMode(themeMode);

  void _updateProfileLanguageSetting(int langNum) {
    try {
      ProfileDTO newProfile = new ProfileDTO(
          firstName: this.profile.value.firstName,
          lastName: this.profile.value.lastName,
          email: this.profile.value.email,
          settings: this.profile.value.settings);

      updateProfile(newProfile);
    } catch (e) {
      Log.debug(e);
    }
  }
}
